package com.zenchn.service.impl;


import com.zenchn.dao.TSysAreasMapper;
import com.zenchn.dynamic.TSysAreasDynamicMapper;
import com.zenchn.entity.AreaTreeVO;
import com.zenchn.generic.GenericDao;
import com.zenchn.generic.GenericServiceImpl;
import com.zenchn.model.TSysAreas;
import com.zenchn.model.TSysAreasExample;
import com.zenchn.service.AreasService;
//import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import static org.mybatis.dynamic.sql.SqlBuilder.*;
import static com.zenchn.dynamic.TSysAreasDynamicSqlSupport.*;
/**
 * 地区 信息Service实现类
 *
 * @author dingxinfa
 * @date 2020-04-16
 */
@Service
@Transactional(rollbackFor = Exception.class)
public class AreasServiceImpl extends GenericServiceImpl<TSysAreas, String, TSysAreasExample> implements AreasService {

    @Resource
    private TSysAreasMapper areasMapper;

	@Resource
	private TSysAreasDynamicMapper areasDynamicMapper;

	@Override
	public GenericDao<TSysAreas, String, TSysAreasExample> getDao() {
		return areasMapper;
	}

	@Override
	public List<TSysAreas> selectByParentId(String code) {
		TSysAreasExample example=new TSysAreasExample();
		example.createCriteria().andParentCodeEqualTo(code);
		
		return areasMapper.selectByExample(example);
	}

	@Override
	public List<TSysAreas> selectByParentIdAndIsEnable(String code) {
		TSysAreasExample example=new TSysAreasExample();
		example.createCriteria().andParentCodeEqualTo(code).andIsEnableEqualTo(true);

		return areasMapper.selectByExample(example);
	}



	@Override
	public LinkedList<TSysAreas> findFullCascade(String code) {
		return fullCascadeArea(new LinkedList<TSysAreas>(), code);
	}
	
	private LinkedList<TSysAreas> fullCascadeArea(LinkedList<TSysAreas> areas, String id) {
		TSysAreas area= areasMapper.selectByPrimaryKey(id);
		if(null!=area){
			areas.add(0, area);
		}
		if(null!= area && null!= area.getParentCode()&& !"0".equals(area.getParentCode())){
			fullCascadeArea(areas,area.getParentCode());
		}
		return areas;
	}


	@Override
	//@Cacheable(value = "monitor-early-warning:cache:2hours", key="'areas.selectCodeByParentCode:'+#code",unless="#result == null")
	public List<String> selectCodeByParentCode(String code) {
		TSysAreas areas=areasMapper.selectByPrimaryKey(code);
		if (null!=areas) {
			List<TSysAreas> areaList = this.selectByLikeShortCode(areas.getShortCode(), null);

			List<String> codeList = new ArrayList<String>();
			for (TSysAreas area : areaList) {
				codeList.add(area.getCode());
			}
			return codeList;
		}
		return null;
	}

	@Override
	public List<TSysAreas> selectByLikeShortCode(String shortCode, List<String> gradeList) {
		TSysAreasExample areasExample=new TSysAreasExample();
		TSysAreasExample.Criteria criteria= areasExample.createCriteria();

		if (null!=shortCode && !"".equals(shortCode.trim())){
			criteria.andShortCodeLike(shortCode.trim()+"%");
		}
		if (null!=gradeList && !gradeList.isEmpty()){
			criteria.andGradeIn(gradeList);
		}
		return areasMapper.selectByExample(areasExample);
	}

	@Override
	public Boolean verifyName(String parentCode, String code, String name) {
		TSysAreasExample areasExample=new TSysAreasExample();
		TSysAreasExample.Criteria criteria= areasExample.createCriteria();

		criteria.andParentCodeEqualTo(parentCode);
		criteria.andNameEqualTo(name);
		if (null !=code) {
			criteria.andCodeNotEqualTo(code);
		}
		if(areasMapper.countByExample(areasExample)>0){
			return false;
		}
		return true;
	}

	@Override
	//@Cacheable(value = "monitor-early-warning:cache:2minutes", key="'getAreaTreebyAreaCodeAndIsEnable:'+#code",unless="#result == null")
	public List<AreaTreeVO> getAreaTreebyAreaCodeAndIsEnable(String code) {
		List<TSysAreas> areasList=new ArrayList<>();
		if (null!=code && !"".equals(code.trim())){
			areasList.add(areasMapper.selectByPrimaryKey(code));
		}else {
			TSysAreasExample areasExample = new TSysAreasExample();
			areasExample.createCriteria().andIsEnableEqualTo(true).andGradeEqualTo("1");
			areasList=areasMapper.selectByExample(areasExample);
		}
		List<AreaTreeVO> areaTreeVOList = getAreaTreeVOList(areasList);
		areaTreeVOList.forEach( areaTree ->{
			if (Integer.parseInt(areaTree.getGrade()) < 5) {
				areaTree.setChildren(getSubsetAreaTree(areaTree.getCode()));
			}
		});
		return areaTreeVOList;
	}

	private List<AreaTreeVO>  getSubsetAreaTree(String code){
		List<AreaTreeVO> subsetAreaTree = new ArrayList<>();

		TSysAreasExample areasExample = new TSysAreasExample();
		areasExample.createCriteria().andParentCodeEqualTo(code).andIsEnableEqualTo(true);
		subsetAreaTree=this.getAreaTreeVOList(areasMapper.selectByExample(areasExample));
		if (!subsetAreaTree.isEmpty()){
			for (AreaTreeVO areaTree:subsetAreaTree){
				if (Integer.parseInt(areaTree.getGrade()) < 5) {
					areaTree.setChildren(getSubsetAreaTree(areaTree.getCode()));
				}
			}
		}
		return subsetAreaTree;
	}

	private List<AreaTreeVO> getAreaTreeVOList(List<TSysAreas> areasList) {
		List<AreaTreeVO> areaTreeVOList = new ArrayList<>();
		for (TSysAreas areas : areasList) {
			AreaTreeVO areaTreeVO = new AreaTreeVO();
			areaTreeVO.setCode(areas.getCode());
			areaTreeVO.setGrade(areas.getGrade());
			areaTreeVO.setName(areas.getName());
			areaTreeVO.setParentCode(areas.getParentCode());
			if (Integer.parseInt(areas.getGrade()) < 5) {
				areaTreeVO.setLeaf(false);
			}else{
				areaTreeVO.setLeaf(true);
			}
			areaTreeVOList.add(areaTreeVO);
		}
		return areaTreeVOList;
	}

}
